/**
 * 
 */
package co.droidforum.foodx.ws;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;

import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpRequest;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.client.ClientHttpRequestExecution;
import org.springframework.http.client.ClientHttpRequestInterceptor;
import org.springframework.http.client.ClientHttpResponse;

import co.droidforum.foodx.utils.DroidEncryption;

/**
 * @author andres.alzate
 *
 */
public class ClientHttpRequestInterceptorHandler implements ClientHttpRequestInterceptor {

	/**
	 * Intercepta la respuesta que se ha obtenido del servidor para poderla
	 * tratar y saber si ocurrio un error de negocio o de comunicacion
	 * con el seb service
	 */
	public ClientHttpResponse intercept(HttpRequest request, byte[] datos, ClientHttpRequestExecution clientHttpRequestExecution) throws IOException {
		try {
			
			final ClientHttpResponse response;
			
			if(datos != null && datos.length != 0){
				response = clientHttpRequestExecution.execute(request, DroidEncryption.encrypt(datos));
			}else{
				response = clientHttpRequestExecution.execute(request, datos);
			}
			
			ClientHttpResponse clientHttpResponse = new ClientHttpResponse() {
				
				public HttpHeaders getHeaders() {
					return response.getHeaders();
				}
				
				public InputStream getBody() throws IOException {
					
					InputStream in = null;
					try {
						in = response.getBody();
						ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
						int c;
						while ((c = in.read()) != -1) {
							byteArrayOutputStream.write((char)c);
						}
						
						//Flujo de bytes a descifrar
						byte[] buffer = byteArrayOutputStream.toByteArray();
						
						//Buffer decodificado
						if(!response.getHeaders().getContentType().equals(MediaType.APPLICATION_OCTET_STREAM) && buffer != null && buffer.length != 0){
							buffer = DroidEncryption.decrypt(buffer);
						}
					
						return new ByteArrayInputStream(buffer);
					} catch (IOException e) {
						return null;
					}
				}
				
				public String getStatusText() throws IOException {
					return response.getStatusText();
				}
				
				public HttpStatus getStatusCode() throws IOException {
					return response.getStatusCode();
				}
				
				public void close() {
					response.close();
				}
			};
			
			return clientHttpResponse;
		} catch (Exception e) {
			throw new RemoteConnectionServiceException(e);
		}
	}
}